use bytes::Bytes;
use csv::StringRecord;
use encoding::all::GBK;
use encoding::{DecoderTrap, EncoderTrap, Encoding};
use serde::{Deserialize, Serialize};
use serde_json;
use std::error::Error;
use std::io;
use std::io::Read;

/// 股票价格
#[derive(Debug, Serialize, Deserialize)]
pub struct HistoricalStockQuote {
    #[serde(rename(deserialize = "股票代码"))]
    pub code: String,

    #[serde(rename(deserialize = "名称"))]
    pub name: String,

    #[serde(rename(deserialize = "日期"))]
    pub date: String, //yyyy-MM-dd

    #[serde(rename(deserialize = "开盘价"))]
    pub topen: f64,

    #[serde(rename(deserialize = "收盘价"))]
    pub tclose: f64,

    #[serde(rename(deserialize = "涨跌幅"))]
    pub pchg: f64,

    #[serde(rename(deserialize = "涨跌额"))]
    pub chg: f64,

    #[serde(rename(deserialize = "总市值"))]
    pub tcap: f64,

    #[serde(rename(deserialize = "流通市值"))]
    pub mcap: f64,

    #[serde(rename(deserialize = "成交量"))]
    pub voturnover: f64,

    #[serde(rename(deserialize = "成交金额"))]
    pub vaturnover: f64,

    #[serde(rename(deserialize = "换手率"))]
    pub turnover: f64,
}

impl HistoricalStockQuote {
    pub fn parse_from_csv(csv_data: &Bytes) -> Vec<HistoricalStockQuote> {
        let mut result = vec![];
        let data = GBK.decode(csv_data.as_ref(), DecoderTrap::Strict).unwrap();
        let mut rdr = csv::Reader::from_reader(data.as_bytes());
        for record in rdr.deserialize::<HistoricalStockQuote>() {
            //rdr.deserialize::<HistoricalStockQuote>()
            if let Ok(mut record) = record {
                record.code = record.code.replace("\'", "");
                result.push(record);
            }
        }
        result
    }
}
